package espi_pkg;

//eSPI Slave Registers offset addresses, from eSPI header
typedef enum logic [15:0] {		EP_CONTROL_OFFSET			=	16'h00_00,	// Endpoint CONTROL Register
								EP_STATUS_OFFSET			=	16'h00_10,	// Endpoint STATUS Register
								EP_ERROR_OFFSET				= 	16'h00_20,	// Endpoint ERROR Register
								EP_CH0_PKT_SIZE_OFFSET		=	16'h00_50,	// Channel 0 Packet Size = Sets Tx AVAIL Threshold
								EP_CH1_PKT_SIZE_OFFSET		=	16'h00_40,	// Channel 1 Packet Size = Sets Tx AVAIL Threshold
								EP_CH2_PKT_SIZE_OFFSET		=	16'h00_30,	// Channel 2 Packet Size = Sets Tx AVAIL Threshold
								EP_CH3_PKT_SIZE_OFFSET		=	16'h00_60,	// Channel 3 Packet Size = Sets Tx AVAIL Threshold
								EP_SCR_PKT_SIZE_OFFSET		=	16'h00_70,	// SCRATCH Packet Size = Sets Tx->Rx AVAIL Threshold
								EP_COMMAND_OFFSET			=	16'h00_90,	// "Mirrored" Copy of COMMAND Written by ESPI Master
								EP_DEVICE_ID_OFFSET			=	16'h00_80,	// "Mirrored" Device Identification
								EP_GENERAL_CONFIG_OFFSET	=	16'h01_00,	// "Mirrored" General Capabilities and Configurations
								EP_CHANNEL_0_CONFIG_OFFSET	= 	16'h01_10,	// "Mirrored" Channel 0 Capabilities and Configurations
								EP_CHANNEL_1_CONFIG_OFFSET	= 	16'h01_20,	// "Mirrored" Channel 1 Capabilities and Configurations
								EP_CHANNEL_2_CONFIG_OFFSET	= 	16'h01_30,	// "Mirrored" Channel 2 Capabilities and Configurations
								EP_CHANNEL_3_CONFIG_OFFSET	= 	16'h01_40,
								// FIFO ADDRESSES
								PC_BASE_ADDR            	=    { 4'h0, 4'b0010, 8'h00 },    // Peripheral Posted/Completion RXQ/TXQ Base Address
								NP_BASE_ADDR            	=    { 4'h0, 4'b0100, 8'h00 },    // Peripheral Non-Posted RXQ/TXQ Base Address

								VWIRE_BASE_ADDR         	=    { 4'h0, 4'b0110, 8'h00 },    // Virtual Wire RXQ/TXQ Base Address
								OOB_BASE_ADDR           	=    { 4'h0, 4'b1000, 8'h00 },    // Out-of-Band (SMBus) RXQ/TXQ Base Address

								FLASH_C_BASE_ADDR       	=    { 4'h0, 4'b1010, 8'h00 },    // Flash Access Completion RXQ/TXQ Base Address
								FLASH_NP_BASE_ADDR      	=    { 4'h0, 4'b1100, 8'h00 },    // Flash Access Non-Posted RXQ/TXQ Base Address

								SCR_BASE_ADDR           	=    { 4'h0, 4'b1110, 8'h00 },    // Scratch Register Base Address
								MASK_BASE_ADDR          	=    { 4'hf, 4'b1110, 8'h00 }    // Lower 9 Bits = Offset
							} EspiAvmmAddrEnumType;	//
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
// **Capabilities and Configuration Register(s)**
parameter 		VERSION_ID              =   8'h01,                  // Indicates compliance to specific eSPI specification revision.
				IO_MODE_SUPPORT         =   2'b11,                  // I/O Mode Support
				OD_ALERT_SUPPORT        =   1'b0,                   // Open Drain Alert# Supported
				MAX_FREQ_SUPPORT        =   3'b011,                 // Maximum Frequency Supported
				MAX_WAIT_STATE			=	3'b000;					// Maximum WAIT STATE Allowed

parameter       CH0_MAX_PAYLOAD          =   3'b001,                 // Peripheral Channel Maximum Payload Size Supported
				CH1_MAX_COUNT            =   6'b000111,             	// Maximum Virtual Wire Count Supported (this is a 0-based count)
				CH2_MAX_PAYLOAD          =   3'b111,                 // OOB Message Channel Maximum Payload Size Supported
				CH3_MAX_PAYLOAD          =   3'b001;                 // Flash Access Channel Maximum Payload Size Supported
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
// **FREE, AVAIL Thresholds**
parameter		CH0_AVAIL_THRESHOLD		=	32'd2,					// Peripheral Channel Message Available Threshold (0-based count)
				CH1_AVAIL_THRESHOLD		=	32'd2,					// Virtual Wire Channel Message Available Threshold (0-based count)
				CH2_AVAIL_THRESHOLD		=	32'd6,					// OOB Message Channel Message Available Threshold (0-based count)
				CH3_AVAIL_THRESHOLD		=	32'd2,					// Flash Access Channel Message Available Threshold (0-based count)
				SCR_AVAIL_THRESHOLD		=	32'd0;					// SCRATCH Register Message Available Threshold (0-based count)
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
// **QUEUE Base Addresses**
// parameter       PC_BASE_ADDR            =    { 4'h0, 4'b0010, 8'h00 },    // Peripheral Posted/Completion RXQ/TXQ Base Address
				// NP_BASE_ADDR            =    { 4'h0, 4'b0100, 8'h00 },    // Peripheral Non-Posted RXQ/TXQ Base Address

                // VWIRE_BASE_ADDR         =    { 4'h0, 4'b0110, 8'h00 },    // Virtual Wire RXQ/TXQ Base Address
                // OOB_BASE_ADDR           =    { 4'h0, 4'b1000, 8'h00 },    // Out-of-Band (SMBus) RXQ/TXQ Base Address

                // FLASH_C_BASE_ADDR       =    { 4'h0, 4'b1010, 8'h00 },    // Flash Access Completion RXQ/TXQ Base Address
                // FLASH_NP_BASE_ADDR      =    { 4'h0, 4'b1100, 8'h00 },    // Flash Access Non-Posted RXQ/TXQ Base Address

                // SCR_BASE_ADDR           =    { 4'h0, 4'b1110, 8'h00 },    // Scratch Register Base Address
                // MASK_BASE_ADDR          =    { 4'hf, 4'b1110, 8'h00 };    // Lower 9 Bits = Offset

/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
// ********************Slave Register Offsets**
parameter     DEVICE_ID_OFFSET          =	16'h00_04,               // Device Identification
              GENERAL_CONFIG_OFFSET     =	16'h00_08,               // General Capabilities and Configurations

              CHANNEL_0_CONFIG_OFFSET   =	16'h00_10,               // Channel 0 Capabilities and Configurations
              CHANNEL_1_CONFIG_OFFSET   =	16'h00_20,               // Channel 1 Capabilities and Configurations

              CHANNEL_2_CONFIG_OFFSET   =	16'h00_30,               // Channel 2 Capabilities and Configurations
              CHANNEL_3_CONFIG_OFFSET   =	16'h00_40,               // Channel 3 Capabilities and Configurations

              COMMAND_OFFSET            =	16'h00_00,               // Command Opcode
              RESPONSE_OFFSET           =	16'h00_01,               // Response Opcode
              STATUS_OFFSET             =	16'h00_02,               // Status Register

              HEADER_OFFSET             =	16'h08_00,               // Header Queue
              DATA_OFFSET               =	16'h10_00;               // Data Queue
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
// ********************Command Opcode Encodings**
typedef enum logic [7:0] {  PUT_PC          = 	8'b0000_0000,            // Put a posted or completion header and optional data.
							GET_PC          = 	8'b0000_0001,            // Get a posted or completion header and optional data.

							PUT_NP           =	8'b0000_0010,            // Put a non-posted header and optional data.
							GET_NP           =	8'b0000_0011,            // Get a non-posted header and optional data.

							PUT_IORD_SHORT_BYTE   =	8'b0100_00??,            // Put a short (1, 2 or 4 bytes) non-posted I/O Read packet.
							PUT_IOWR_SHORT_BYTE   =	8'b0100_01??,            // Put a short (1, 2 or 4 bytes) non-posted I/O Write packet.

							PUT_MEMRD32_SHORT_BYTE	=	8'b0100_10??,            // Put a short (1, 2 or 4 bytes) non-posted Memory Read 32 packet.
							PUT_MEMWR32_SHORT_BYTE	=	8'b0100_11??,            // Put a short (1, 2 or 4 bytes) posted Memory Write 32 packet.

/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
							PUT_VWIRE         =  8'b0000_0100,            // Put a Tunneled virtual wire packet.
							GET_VWIRE         =  8'b0000_0101,            // Get a Tunneled virtual wire packet.
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
							PUT_OOB           =  8'b0000_0110,            // Put an OOB (Tunneled SMBus) message.
							GET_OOB           =  8'b0000_0111,            // Get an OOB (Tunneled SMBus) message.
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
							PUT_FLASH_C       =  8'b0000_1000,            // Put a Flash Access completion.
							GET_FLASH_NP      =  8'b0000_1001,            // Get a non-posted Flash Access request.
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
							GET_STATUS        =  8'b0010_0101,            // Command initiated by the master to read the status register of the slave.
							SET_CONFIGURATION =  8'b0010_0010,            // Command to set the capabilities of the slave as part of the initialization. This is typically done after the master discovers the capabilities of the slave.
							GET_CONFIGURATION =  8'b0010_0001,            // Command to discover the capabilities of the slave as part of the initialization.
							RESET             =  8'b1111_1111}            // In-band RESET command.
							eSPI_Command_Opcode_Enum;
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
// ********************Request Length Encodings**
typedef	enum logic[1:0] {	ONE_BYTE           =         2'b00,                   // 1 byte
							TWO_BYTES          =         2'b01,                   // 2 bytes
							FOUR_BYTES         =         2'b11}                   // 4 bytes
							eSPI_ReqLenEnumType;
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
// ********************Channel Encodings**
parameter      			PERIPHERAL_CHANNEL     =     2'd0,                    // Peripheral Channel
						VIRTUAL_WIRE_CHANNEL   =     2'd1,                    // Virual Wire Channel
						OOB_MESSAGE_CHANNEL    =     2'd2,                    // OOB Message Channel
						FLASH_ACCESS_CHANNEL   =     2'd3;                    // Flash Access Channe
////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
// ********************Cycle Type Encodings**
typedef enum logic[7:0] {	MEMORY_READ_32      		=        8'b0000_0000,            // 32 bit addressing Memory Read Request.
							MEMORY_READ_64      		=        8'b0000_0010,            // 64 bit addressing Memory Read Request.
							MEMORY_WRITE_32     		=        8'b0000_0001,            // 32 bit addressing Memory Write Request.
							MEMORY_WRITE_64     		=        8'b0000_0011,            // 64 bit addressing Memory Write Request.

							LOCAL_MESSAGE       		=       8'b0001_0000,            // Message Request.  Local – Terminated at receiver.
							LOCAL_MESSAGE_DATA   		=       8'b0001_0001,            // Message Request with data payload.  Local – Terminated at receiver.
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
							SUCCESSFUL_COMPLETE_NO_DATA		=  		8'b0000_0110,            // Successful Completion Without Data. Corresponds to I/O Write, Flash Write or Flash Erase.
							SUCCESSFUL_COMPLETE_DATA_SM		=  		8'b0000_1001,            // Successful Completion With Data, Indicates the middle completion of a split completion sequence. Corresponds to Memory Read, I/O Read or Flash Read.
							SUCCESSFUL_COMPLETE_DATA_SF		=  		8'b0000_1011,            // Successful Completion With Data, Indicates the first completion of a split completion sequence. Corresponds to Memory Read, I/O Read or Flash Read.
							SUCCESSFUL_COMPLETE_DATA_SL		=  		8'b0000_1101,            // Successful Completion With Data, Indicates the last completion of a split completion sequence. Corresponds to Memory Read, I/O Read or Flash Read.
							SUCCESSFUL_COMPLETE_DATA_SO		=  		8'b0000_1111,            // Successful Completion With Data, Indicates the only completion for a split transaction. Corresponds to Memory Read, I/O Read or Flash Read.
							UNSUCCESSFUL_COMPLETE_SM   		=  		8'b0000_1000,            // Unsuccessful Completion Without Data, Indicates the middle completion of a split completion sequence. Corresponds to Memory, I/O or Flash accesses.
							UNSUCCESSFUL_COMPLETE_SF   		=  		8'b0000_1010,            // Unsuccessful Completion Without Data, Indicates the first completion of a split completion sequence. Corresponds to Memory, I/O or Flash accesses.
							UNSUCCESSFUL_COMPLETE_SL   		=  		8'b0000_1100,            // Unsuccessful Completion Without Data, Indicates the last completion of a split completion sequence. Corresponds to Memory, I/O or Flash accesses.
							UNSUCCESSFUL_COMPLETE_SO   		=  		8'b0000_1110,            // Unsuccessful Completion Without Data, Indicates the only completion for a split transaction. Corresponds to Memory, I/O or Flash accesses.


/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
							OOB_MESSAGE              	=  8'b0010_0001,            // SMBus Out-Of-Band Message. SMBus packet tunneling.
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
							// FLASH_READ                =  8'b0000_0000,            // Read from Flash.
							// FLASH_WRITE               =  8'b0000_0001,            // Write to Flash.
							// FLASH_ERASE               =  8'b0000_0010,            // Flash Erase instruction. Erase part or the whole partition owned by the corresponding flash master.
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
							NULL                      =  8'b1111_1111}            // Null.
							eSPI_CycleTypeEnum;

/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
// ********************Response Field Encodings**
typedef enum logic [7:0] {	ACCEPT              =        8'b0000_1000,            // Command was successfully received. If the command was a PUT_NP, a response of ACCEPT means that the non-posted transaction is being completed as a “connected” transaction.
							DEFER               =        8'b0000_0001,            // Only valid in response to a PUT_NP. A nonposted command was successfully received, and completing the non-posted transaction is deferred to a future split completion.
							NON_FATAL_ERROR     =        8'b0000_0010,            // The received command had an error with nonfatal severity. The error does not affect the ability to process the received command.
							FATAL_ERROR         =        8'b0000_0011,            // The received command had a fatal error that prevented the transaction layer packet from being successfully processed. Fatal errors include malformed transactions, Put without Free, Get without Avail and etc.
							WAIT_STATE          =        8'b0000_1111,            // Adds one byte-time of delay when responding to a transaction on the bus.
							NO_RESPONSE         =        8'b1111_1111}            // The response encoding of all 1’s is defined as no response.
							eSPI_ResponseFieldEnumType;
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
// ********************Append Encodings**
typedef enum logic [1:0] {	NO_APPEND            =       2'b00,                  // No append.
							PERIPHERAL_APPEND    =       2'b01,                  // A Peripheral (channel 0) completion is appended.
							VIRTUAL_WIRE_APPEND  =       2'b10,                  // A Virtual Wire (channel 1) packet is appended.
							FLASH_ACCESS_APPEND  =       2'b11}                  // A Flash Access (channel 3) completion is appended. This is only applicable when slave attached flash sharing is supported and in operation.
							eSPI_Append_EnumType;
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
// ********************Status Field Encodings********************
parameter     PC_FREE            =         4'd0,                    // When ‘1’, indicates the slave is free to accept at least one channel 0 peripheral posted or completion header and data up to maximum payload size.
              NP_FREE            =         4'd1,                    // When ‘1’, indicates the slave is free to accept at least one channel 0 peripheral non-posted header and 1 DW of Data (if applicable).
              VWIRE_FREE         =         4'd2,                    // This bit must be always a ‘1’. Tunneling of channel 1 virtual wires is not flow controlled.
              OOB_FREE           =         4'd3,                    // When ‘1’, indicates the slave is free to accept at least one channel 2 OOB (tunneled SMBus) message with data up to maximum payload size.

              PC_AVAIL           =         4'd4,                    // When ‘1’, indicates the slave has a channel 0 peripheral posted or completion header and optional data up to maximum payload size available to send.
              NP_AVAIL           =         4'd5,                    // When ‘1’, indicates the slave has a channel 0 peripheral non-posted header available to send.
              VWIRE_AVAIL        =         4'd6,                    // When ‘1’, indicates the slave has a channel 1 tunneled virtual wire available to send.
              OOB_AVAIL          =         4'd7,                    // When ‘1’, indicates the slave has a channel 2 OOB (tunneled SMBus) message with data up to maximum payload size available to send.

              FLASH_C_FREE       =         4'd8,                    // When ‘1’, indicates the slave is free to accept at least one channel 3 Flash Access completion header and data up to maximum payload size. This bit must be always a ‘1’.
              FLASH_NP_FREE      =         4'd9,                    // When ‘1’, indicates the slave is free to accept at least one channel 3 Flash Access non-posted header and data up to maximum payload size.

              FLASH_C_AVAIL      =         4'd12,                   // When ‘1’, indicates the slave has a channel 3 Flash Access completion header and data up to maximum payload size available to send.
              FLASH_NP_AVAIL     =         4'd13,                   // When ‘1’, indicates the slave has a channel 3 Flash Access non-posted header and data up to maximum payload size available to send.

              SCR_FREE           =         5'd16,                   // When ‘1’, indicates the slave is free to accept at least (4) bytes from Scratch Register.
              SCR_AVAIL          =         5'd17;                   // When ‘1’, indicates the slave has at least (1) byte from Scratch Register to send.
/////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////
// ********************Error Offset Encodings********************
parameter	INVALID_COMMAND         =    6'd0,                    // Invalid Command Opcode
			INVALID_CYCLE_TYPE      =    6'd1,                    // Invalid Cycle Type
			CRC_ERROR               =    6'd2,                    // Command phase CRC Error
			DEASSERT_CS_N           =    6'd3,                    // Unexpected deassertion of Chip Select#

			PUT_WITHOUT_FREE        =    6'd4,                    // PUT without FREE
			GET_WITHOUT_AVAIL       =    6'd5,                    // GET without AVAIL

			CH0_MALFORMED_PACKET    =    6'd8,                    // Peripheral Channel: Malformed Packet during Command Phase
			CH1_MALFORMED_PACKET    =    6'd9,                    // Virtual Wire Channel: Malformed Packet during Command Phase
			CH2_MALFORMED_PACKET    =    6'd10,                   // OOB Channel: Malformed Packet during Command Phase
			CH3_MALFORMED_PACKET    =    6'd11;                   // Flash Access Channel: Malformed Packet during Command Phase


typedef struct packed {
	eSPI_CycleTypeEnum CycleType;
	logic [3:0] 	Tag;
	logic [11:0] 	Len;
	logic [31:0] 	Addr31_0;						// For 32 bit address, use upper address only
	logic [31:0] 	Addr63_32;						// For 64 bit address, use upper and lower address.
	} eSPIPeriChHDR11BtypeS;


typedef enum logic [5:0] {
		PUT_IORD_SHORT   =		6'b0100_00,            // Put a short (1, 2 or 4 bytes) non-posted I/O Read packet.
		PUT_IOWR_SHORT   =		6'b0100_01,            // Put a short (1, 2 or 4 bytes) non-posted I/O Write packet.
		PUT_MEMRD32_SHORT	=	6'b0100_10,            // Put a short (1, 2 or 4 bytes) non-posted Memory Read 32 packet.
		PUT_MEMWR32_SHORT	=	6'b0100_11           // Put a short (1, 2 or 4 bytes) posted Memory Write 32 packet.
} ShortCMDEnumType;

typedef struct packed {
	ShortCMDEnumType CMD;
	eSPI_ReqLenEnumType Len;
	logic [15:0] Addr15_0;
	logic [15:0] Addr31_16;
} eSPIPeriChHDR5BtypeS;



typedef struct packed {
	logic [7:0] 	GroupLen; // Number of Groups (Index + Data) in packet
} PutVWireWriteTypeS;


// Header Size in Bytes for various CycleTypes
parameter  	MW32HeaderSize 						= 12'd7,
			MW64HeaderSize 						= 12'd11,
			MSGHeaderSize 						= 12'd8,
			UnSuccessfulCompletionHeaderSize 	= 12'd3,
			SuccessfulCompletionHeaderSize		= 12'd3,
			VirtualWireHeaderSize				= 12'd1,
			OOBMessageHeaderSize				= 12'd3,
			ShortCommandHeaderSize				= 12'd4;




endpackage
